/**
 * author:Administrator
 * date:2016/3/16
 * desc:TODO
 */

"use strict";

let RawQuery = require('./_RawQuery.js');
class CagegoryQuery extends RawQuery {
  constructor() {
    super();
  }

  * findAll() {
    yield this.__initCache();
    return CagegoryQuery.cachedItem;
  }

  * findRoot() {
    yield this.__initCache();
    let ids = Object.keys(CagegoryQuery.idTree).map(id=>parseInt(id));
    return CagegoryQuery.cachedItem.filter(item => ids.indexOf(item.id) >= 0);
  }

  * findById(id) {
    yield this.__initCache();
    return CagegoryQuery.cachedItem[id];
  }

  * findChild(pid) {
    yield this.__initCache();
    if (pid == CagegoryQuery.rootPid) {
      return CagegoryQuery.cachedItem;
    }
    if (!CagegoryQuery.cachedItem[pid]) {
      return [];
    }
    let arr = CagegoryQuery.idPath(pid);
    let node = CagegoryQuery.idTree;
    while (arr.length > 0) {
      node = node[arr.pop()];
    }

    // 寻找该 id下的所有child 的id
    function foo(aNode, arr) {
      let list = Object.keys(aNode);
      // console.log(list);
      if (list.length == 0)return;
      for (let key of list) {
        arr.push(key);
        foo(aNode[key], arr);
      }
    }

    let allIds = [];
    foo(node, allIds);

    allIds = allIds.map(idStr => parseInt(idStr));
    return CagegoryQuery.cachedItem.filter(item => allIds.indexOf(item.id) >= 0);
  }

  // 寻找该id 到 root之间的一条路径
  static idPath(id) {
    let cachedItem = CagegoryQuery.cachedItem;
    let arr = [id];
    let item = cachedItem.filter(o => o.id == id)[0];
    let pid = item.pid;
    while (pid != CagegoryQuery.rootPid) {
      item = cachedItem.filter(o => o.id == pid)[0];
      arr.push(pid);
      pid = item.pid;
    }
    return arr;
  }

  * __initCache(forceInvalid) {
    if (!forceInvalid && CagegoryQuery.cachedItem) {
      return;
    }

    let sql = "select * from category";
    let cachedItem = yield this.query(sql);
    cachedItem = Object.freeze(cachedItem);
    CagegoryQuery.cachedItem = cachedItem;

    // build id tree
    let idTree = {};
    let remains = cachedItem.map(item => {
      return {id: item.id, pid: item.pid}
    });

    while (remains.length > 0) {
      let item = remains.pop();
      let ids = CagegoryQuery.idPath(item.id);

      let pItem = idTree;
      while (ids.length > 0) {
        let id = ids.pop();
        if (!pItem[id]) pItem[id] = {};
        pItem = pItem[id];
      }
    }

    idTree = Object.freeze(idTree);
    CagegoryQuery.idTree = idTree;

    console.log('cachedItem', cachedItem);
    console.log('idTree', idTree);
  }

  // 局部更新更好
  invalidCache(entity) {
    // console.log('invalid category cache');
    CagegoryQuery.cachedItem = null;
    CagegoryQuery.idTree = null;
  }
}

CagegoryQuery.cachedItem = null;
CagegoryQuery.idTree = null;
CagegoryQuery.rootPid = 0;

module.exports = new CagegoryQuery();
